﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using SIMA.Entities;
using SIMA.Core.Security;

namespace SIMA.Services
{
    #region Base AsyncResult

    public class AsyncResult : IAsyncResult, IDisposable
    {
        private AsyncCallback m_AsyncCallback;
        private object m_State;
        private ManualResetEvent m_ManualResentEvent;
        private Profile profile;

        public AsyncResult(Profile profile, AsyncCallback callback, object state)
        {
            this.m_AsyncCallback = callback;
            this.m_State = state;
            this.m_ManualResentEvent = new ManualResetEvent(false);
            this.profile = profile;
        }

        #region Miembros de IAsyncResult

        public object AsyncState
        {
            get
            {
                return m_State;
            }
        }

        public System.Threading.WaitHandle AsyncWaitHandle
        {
            get
            {
                return m_ManualResentEvent;
            }
        }

        public bool CompletedSynchronously
        {
            get
            {
                return false;
            }
        }

        public bool IsCompleted
        {
            get
            {
                return m_ManualResentEvent.WaitOne(0, false);
            }
        }

        #endregion

        #region Miembros de IDisposable
        private bool m_IsDisposed = false;
        private event System.EventHandler m_Disposed;


        [System.ComponentModel.Browsable(false)]
        public bool IsDisposed
        {
            get
            {
                return m_IsDisposed;
            }
        }

        public event System.EventHandler Disposed
        {
            add
            {
                m_Disposed += value;
            }
            remove
            {
                m_Disposed -= value;
            }
        }

        public void Dispose()
        {
            if (!m_IsDisposed)
            {
                this.Dispose(true);
                System.GC.SuppressFinalize(this);
            }
        }

        protected virtual void Dispose(bool disposing)
        {
            try
            {
                if (disposing)
                {
                    m_ManualResentEvent.Close();
                    m_ManualResentEvent = null;
                    m_State = null;
                    m_AsyncCallback = null;

                    System.EventHandler handler = m_Disposed;
                    if (handler != null)
                    {
                        handler(this, System.EventArgs.Empty);
                        handler = null;
                    }
                }
            }
            finally
            {
                m_IsDisposed = true;
            }
        }

        protected void CheckDisposed()
        {
            if (m_IsDisposed)
            {
                string typeName = GetType().FullName;

                // TODO: You might want to move the message string into a resource file
                throw new System.ObjectDisposedException(
                    typeName,
                    String.Format(System.Globalization.CultureInfo.InvariantCulture,
                        "Cannot access a disposed {0}.",
                        typeName));
            }
        }

        #endregion

        public virtual void OnCompleted()
        {
            m_ManualResentEvent.Set();
            if (m_AsyncCallback != null)
            {
                m_AsyncCallback(this);
            }
        }
    }

    #endregion

    #region Perfil

    public class PerfilesAsyncResult : AsyncResult
    {
        private List<T_C_Perfil> collectionResult;
        private Exception exceptionTrace;
        string messageResult;
        Profile profile;        

        public List<T_C_Perfil> CollectionResult
        {
            get { return collectionResult; }
            set { collectionResult = value; }
        }

        public Exception ExceptionTrace
        {
            get { return exceptionTrace; }
            set { exceptionTrace = value; }
        }

        public string MessageResult
        {
            get { return messageResult; }
            set { messageResult = value; }
        }

        public Profile Profile
        {
            get { return profile; }
            set { profile = value; }
        }

        public PerfilesAsyncResult(Profile profile, AsyncCallback callback, object state)
            : base(profile, callback, state)
        {
        }

    }

    #endregion

    #region Equipos

    public class EquiposAsyncResult : AsyncResult
    {
        private List<T_C_Equipo> collectionResult;
        private Exception exceptionTrace;
        string messageResult;
        Profile profile;

        public List<T_C_Equipo> CollectionResult
        {
            get { return collectionResult; }
            set { collectionResult = value; }
        }

        public Exception ExceptionTrace
        {
            get { return exceptionTrace; }
            set { exceptionTrace = value; }
        }

        public string MessageResult
        {
            get { return messageResult; }
            set { messageResult = value; }
        }

        public Profile Profile
        {
            get { return profile; }
            set { profile = value; }
        }

        public EquiposAsyncResult(Profile profile, AsyncCallback callback, object state)
            : base(profile, callback, state)
        {
        }
    }

    #endregion
}
